// Copyright (c) 2008 Davy Brion (ralinx@davybrion.com)
// All rights reserved.
// 
// Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met:
// 
//     * Redistributions of source code must retain the above copyright notice,
//       this list of conditions and the following disclaimer.
//     * Redistributions in binary form must reproduce the above copyright notice,
//       this list of conditions and the following disclaimer in the documentation
//       and/or other materials provided with the distribution.
//     * Neither the name of Davy Brion nor the names of the
//       contributors may be used to endorse or promote products derived from this
//       software without specific prior written permission.
// 
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
// THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.


using Agatha.Common;
using Agatha.Common.InversionOfControl;
using Source.Common;
using Source.Web.FrameWork;
using System.Reflection;
using System.Linq;
using IConfigurationProvider=Source.Web.FrameWork.IConfigurationProvider;

namespace  Source.Web
{
    public static class ComponentRegistration
	{
        public static void InitializeComponents()
        {
            InitializeAgatha();
            RegisterVariousComponents();
            RegisterAllControllers();
            RegisterAllPartControllers();
        }


        private static void RegisterVariousComponents()
        {
            IoC.Container.Register(typeof(INavigator),typeof(Navigator),Lifestyle.Singleton);
            IoC.Container.Register(typeof(IClientSideUserManager),typeof(UserManager),Lifestyle.Transient);
            IoC.Container.Register(typeof(IFormsAuthentication),typeof(FormsAuthenticationWrapper),Lifestyle.Singleton);
            IoC.Container.Register(typeof(IStateProvider),typeof(WebStateProvider),Lifestyle.Singleton);
            IoC.Container.Register(typeof(IUtilityHelper),typeof(UtilityHelper),Lifestyle.Singleton);
            IoC.Container.Register(typeof(IConfigurationProvider),typeof(ConfigurationProvider),Lifestyle.Singleton);
            IoC.Container.Register(typeof(ITextRepositoryManager),typeof(TextRepositoryManager),Lifestyle.Transient);

        }
        private static void InitializeAgatha()
        {
           var config = new ClientConfiguration(typeof(HelloWorldRequest).Assembly, typeof(Castle.Container))
                            {
                                RequestDispatcherImplementation = typeof(Dispatcher)
                            };
           config.Initialize();
        }
        private static void RegisterAllControllers()
        {
            //IoC.Container.Register(typeof(IController),Assembly.GetExecutingAssembly());
            var typeOfIPartController = typeof(IController);

            foreach (var type in Assembly.GetExecutingAssembly().GetTypes())
            {
                var implementedInterfaces = type.GetInterfaces();

                if (implementedInterfaces.Contains(typeOfIPartController) && !type.IsAbstract && !type.IsGenericType)
                {
                    // the last implemented interface is the one we want
                    ((ICastleContainer)IoC.Container).Register(type, Lifestyle.Transient);
                }
            }
        }

        private static void RegisterAllPartControllers()
        {
            var typeOfIPartController = typeof(IPartController);

            foreach (var type in Assembly.GetExecutingAssembly().GetTypes())
            {
                var implementedInterfaces = type.GetInterfaces();

                if (implementedInterfaces.Contains(typeOfIPartController) && !type.IsAbstract && !type.IsGenericType)
                {
                    // the last implemented interface is the one we want
                    IoC.Container.Register(implementedInterfaces[implementedInterfaces.Length - 1], type, Lifestyle.Transient);
                }
            }
        }

	}
}